package felix.things.router.mqtt.server.broker.config.credentials;

import io.netty.channel.ChannelPipeline;
import io.netty.channel.socket.SocketChannel;
import io.netty.handler.ssl.SslContext;
import io.netty.handler.ssl.SslContextBuilder;
import io.netty.handler.ssl.SslHandler;
import lombok.Data;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;

import javax.net.ssl.KeyManagerFactory;
import javax.net.ssl.SSLEngine;
import java.io.InputStream;
import java.security.KeyStore;

/**
 * @author Felix
 * @date 2019/7/27
 */
@Data
@Component
@ConditionalOnProperty(prefix = "spring.mqtt.broker.credentials", value = "type", havingValue = "cert.PKCS12")
@ConfigurationProperties(prefix = "spring.mqtt.broker.credentials", ignoreInvalidFields = true)
public class CertPKCS12ServerCredentials implements MqttServerCredentials {
    /**
     * SSL密钥文件密码
     */
    private String password = "123456";

    /**
     * SSL密钥文件
     */
    private String pfxFileUrl = "keystore/mqtt-broker.pfx";

    @Override
    public void configureSsl(ChannelPipeline channelPipeline, SocketChannel socketChannel) throws Exception {
        KeyStore keyStore = KeyStore.getInstance("PKCS12");
        InputStream inputStream = this.getClass().getClassLoader().getResourceAsStream(pfxFileUrl);
        keyStore.load(inputStream, password.toCharArray());
        KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");
        kmf.init(keyStore, password.toCharArray());
        SslContext sslContext = SslContextBuilder.forServer(kmf).build();

        SSLEngine sslEngine = sslContext.newEngine(socketChannel.alloc());
        // 服务端模式
        sslEngine.setUseClientMode(false);
        // 不需要验证客户端
        sslEngine.setNeedClientAuth(false);
        channelPipeline.addLast("ssl", new SslHandler(sslEngine));
    }
}
